/*
 * img_tool.h
 *
 *  Created on: 2016年6月18日
 *      Author: guyadong
 */

#ifndef FACEDETECT_IMG_TOOL_H_
#define FACEDETECT_IMG_TOOL_H_
#include <sstream>
#include "detect_cl_types.h"

#ifndef GF_DLL_DECL
#ifdef _WIN32
#ifdef GF_DLL_BUILD
#define GF_DLL_DECL  __declspec(dllexport)
#define GF_DLL_EXTERN
#else
#define GF_DLL_DECL  __declspec(dllimport)
#define GF_DLL_EXTERN
#endif
#else
#define GF_DLL_DECL
#define GF_DLL_EXTERN
#endif
#endif
/*
 * img_tool动态库接口定义
 * 所有接口函数出错的时候会抛出异常
 * */
namespace gdface{
/*
 * 图像工具函数库(解码，显示)
 * */
namespace img_tools{
/*
 * 支持解码的图像格式类型定义
 * */
typedef enum {
	GF_FMT_JPG,// standard JPEG format
	GF_FMT_J2K,// JPEG-2000 format
	GF_FMT_JP2 // JP2 format
}SUPPORTED_FORMAT_TYPE;

/*
 * 将格式为format的图像数据解压缩返回image_matrix_v对象
 * gray为true时图像转灰
 * img_data为null或size为0时抛出异常
 * */
GF_DLL_DECL image_matrix_v decode_image(SUPPORTED_FORMAT_TYPE format,const void*img_data,size_t size,bool gray=false);
/*
 * 显示图像,
 * titlt为图像显示窗口的标题
 * */
GF_DLL_DECL void display(const image_matrix & src_img,const std::string&title="");
inline void display(const image_matrix_v & src_img,const std::string&title=""){
	display(to_image_matrix(src_img),title);
}
/*
 * 对图像数据解码并显示图像,
 * titlt为图像显示窗口的标题
 * */
inline void display(SUPPORTED_FORMAT_TYPE format, const void* img_data, size_t size, const std::string& title = "") {
	display(decode_image(format, img_data, size), title);
}
/*
 * 将检测到的目标(objs_src)以矩形框方式显示在图像上(src_img)
 * norm为true时，objs_src提供的是归一化坐标
 * title为图像显示窗口的标题
 **/
GF_DLL_DECL void display_face_rect(const image_matrix & src_img
		,const object_info_vector& objs_src
		,bool norm
		,const std::string&title=""
		);
inline void display_face_rect(const image_matrix_v & src_img
		,const object_info_vector& objs_src
		,bool norm
		,const std::string&title=""
		){
	return display_face_rect(to_image_matrix(src_img),objs_src,norm,title);
}
// VS2015或支持c++11的编译器下有效
#if _MSC_VER>=1900 || __cplusplus>=201103L
/* 终止递归函数 */
inline void __args_print(std::ostream& steam){}
/* 使用可变参数模板实现参数打印到输出流(ostream)  */
template<typename T,typename ...Args>
inline void __args_print(std::ostream& steam,T first,Args...rest){
	steam<< first;
	__args_print(steam,rest...);
}
/*
 * 支持变长参数的函数模板
 * 将检测到的目标(objs_src)以矩形框方式显示在图像上(src_img)
 * norm为true时，objs_src提供的是归一化坐标
 * 变长参数...args为图像显示窗口的标题
 **/
template<typename ...Args>
static void display_face_rect_t(const image_matrix & src_img
		,const object_info_vector& objs_src
		,bool norm
		,Args&&...args
		){
	auto objects=	norm?convert_def(objs_src,{int(src_img.width),int(src_img.height)}):objs_src;
	std::basic_stringstream<char> stream;
	__args_print(stream,std::forward<Args>(args)...);
	stream<<" "<<objects.size()<<" faces";
	display_face_rect(src_img,objs_src,norm,stream.str());
}
template<typename ...Args>
inline void display_face_rect_t(const image_matrix_v & src_img
		,const object_info_vector& objs_src
		,bool norm
		,Args&&...args
		){
	return display_face_rect_t(to_image_matrix(src_img),objs_src,norm,std::forward<Args>(args)...);
}
#endif

}/*namespace img_tools*/
}/*namespace gdface*/
#endif /* FACEDETECT_IMG_TOOL_H_ */
